#include "StdAfx.h"
#include "Carril.h"
#include <sstream>
using std::vector;
#include "String.h" //TODO: Borar

Carril::Carril()
{	
	numeroPelota = 0;
	distanciaMovida = 0;
	pixels = 0;
	puntosCarril=0;
	puntosBonus=0;
	cantidadPelotas = 0;
	cantidadPelotasEmitidas = 0;
}

Carril::~Carril(void)
{

}

double Carril::CalcularDesplazamientoX(double distancia, double pendiente)
{
	double angulo = atan( pendiente);
	return ( distancia * cos( angulo ) );
}

Pelota* Carril::getPelotaAleatoria(vector<Pelota*> listaPelotasDisponibles)
{
	string nombreAleatorio = "PCarr"; // Para armar el nombre de pelota en el Carril
	char aux[8];
	int highest=2;
	//No anda el size del vector;
	int	cantdePelotas=listaDePelotasDisponibles.size();

	srand((unsigned)time(0)); 
	int random_integer; 
	int lowest=0;
	int range=(highest-lowest)+1; 
	for(int index=0; index<20; index++)
	{ 
		random_integer = lowest+int(range*rand()/(RAND_MAX + 1.0)); 
	}
	
	numeroPelota++;
	itoa(numeroPelota, aux, 10);
	nombreAleatorio.append(aux);
	Pelota* pelotita=listaDePelotasDisponibles[random_integer]->Clonar();
	pelotita->SetNombre(nombreAleatorio);
	return pelotita;
}



void Carril::AgregarPelota()
{
	
	if (this->getCantidadPelotasEmitidas()>0)
	{
		if (((this->getCantidadPelotasEmitidas())%(BOLASAUMENTOVELOCIDAD))==0)
		{
			if (((this->getVelocidad())* (1 + AUMENTOVELOCIDAD))<=MAXIMOVELOCIDAD)
			{
				this->setVelocidad((this->getVelocidad())* (1 + AUMENTOVELOCIDAD));
			}
		}
	}

	if (this->getCantidadPelotasEmitidas()<this->getCantidadPelotas())
		{
			// incremento la cantidad de pelotas
	//		this->setCantidadPelotasEmitidas(this->getCantidadPelotasEmitidas()+1);

			Pelota* pelo= getPelotaAleatoria(this->listaDePelotasDisponibles);
			pelo->setEstaEnCarril(true);
			pelo->SetPuntoIzq( this->listaDePuntos[0]);
			pelo->SetPuntoDer( this->listaDePuntos[1]);
			pelo->setPosX( this->listaDePuntos[0]->getPosX());
			pelo->setPosY( this->listaDePuntos[0]->getPosY());
			pelo->setTramo( 1 );
			//TODO Dani: Definir el random para el color de la pelota

			vector<Pelota*> vect = this->GetListaDePelotas();
			vect.insert(vect.begin(),pelo);
			this->setListaDePelotas(vect);
			this->SumaCantidadPelotas();

	}	
}

void Carril::Recta(Punto *pIzq, Punto *pDer, double *m, double *b)
{
	if (pIzq != NULL && pDer != NULL)
	{
		*m = ( pDer->getPosY() - pIzq->getPosY())/(pDer->getPosX() - pIzq->getPosX());
		*b = pIzq->getPosY() - pIzq->getPosX() * *m ;
	}
}

void Carril::Mover()
{
	//Distancia q se moveran las pelotas por ciclo
	double desplazamiento; //Pixels
	double corrimientoX; //Dani: Cambiar dsp
	vector<Pelota*>::iterator itPelotas;
	int i = 0;
	
	if (this->GetListaDePelotas().empty())
	{
		this->AgregarPelota();//TODO Dani: Definir bien el agregar pelota
		EXIT_SUCCESS;
	}
	
	//Variables para calcular la nueva posicion
	double m, b; // y = m.x + b
	double newPosX, newPosY;
	double x1,x2,y1,y2,dist;
	Punto* pIzq, *pDer;
	vector<Punto*> vPuntos = this->listaDePuntos;
	vector<Punto*>::iterator itPuntos;

	//
	vector<Pelota*> vect = this->listaDePelotas;
	vector<Pelota*>::iterator itAux;
	//

	//for(this->listaDePelotas.begin(); itPelotas != this->listaDePelotas.end(); itPelotas++)
    for(itAux = vect.begin(); itAux < vect.end(); itAux++){

		if (( !(*itAux)->getEstado() ) && (i > 0)) {
			
			x1 = vect.at(i-1)->getPosX();
			y1 = vect.at(i-1)->getPosY();
            x2 = vect.at(i)->getPosX();
			y2 = vect.at(i)->getPosY();
            dist = sqrt(pow((x2 - x1),2)  +  pow((y2 - y1),2)) ;           
			if ( dist < (*itAux)->getRadio())
			{
				(*itAux)->setEstado(vect.at(i-1)->getEstado());
				(*itAux)->setTramo(vect.at(i-1)->getTramo()); //SR
			}

		}
		if ( (*itAux)->getEstado() ){

		pIzq = (*itAux)->GetPuntoIzq();
		pDer = (*itAux)->GetPuntoDer();
		this->Recta(pIzq, pDer, &m, &b); //Recta que describe el tramo
		//Calcular corrimiento en X tal que la velocidad en todos los tramos
		//sea la misma
		corrimientoX = this->CalcularDesplazamientoX(this->GetPixels(), m);
		//Si el tramo se mueve en sentido negativo
		if ( pDer->getPosX() < (*itAux)->getPosX() )
			desplazamiento = corrimientoX * (-1);//Cambio el sentido de movimiento
		else
			desplazamiento = corrimientoX;//Sentido positivo
		
		newPosX = (*itAux)->getPosX() + desplazamiento;
		newPosY = m * newPosX + b;
		
		if ( itAux == vect.begin())
			distanciaMovida += sqrt(pow((newPosX - (*itAux)->getPosX()),2)  +  pow((newPosY - (*itAux)->getPosY()),2));
		//Si se desplazo lo suficiente para que entre una nueva pelota
		if (  distanciaMovida >= (*itAux)->getRadio())
		{
			this->AgregarPelota();
			distanciaMovida = 0;
		}
				
		if ( abs( newPosX - pDer->getPosX() ) <= 1)//Si termina el tramo del Carril
		{
			//Cambio de Tramo de Carril
			pIzq = pDer;
			vPuntos = this->getListaDePuntos();
			for (itPuntos = vPuntos.begin(); itPuntos < vPuntos.end(); itPuntos++)
			{
				if( pIzq->GetId() == (*itPuntos)->GetId())
				{//Busco el proximo punto
					itPuntos++;
					pDer = (*itPuntos);
					//Cambio la pelota de tramo del Carril
					(*itAux)->SetPuntoIzq(pIzq);
					(*itAux)->SetPuntoDer(pDer);
					break;
				}
			}
		}
		//Asigno la nueva posicion a la pelota
		(*itAux)->setPosX(newPosX);
		(*itAux)->setPosY(newPosY);
	}
		i++;
	}
}
vector<Punto*> Carril::getListaDePuntos()
{
	return listaDePuntos;
}

void Carril::setListaDePuntos(vector<Punto*> listPtos)
{
	this->listaDePuntos = listPtos;
}


void Carril::SetId(String valor){
	this->id = valor.tostring(valor.size());
}
String Carril::GetId(){
	return id;
}

string Carril::toString(){

	stringstream resultado;
	resultado << "Carril: " <<std::endl;
	
	for (int i=0; i < (int) this->listaDePuntos.size(); i++){

		Punto* puntoPtr  = this->listaDePuntos.at(i);
		resultado << "punto numero: " << i << " id: " << puntoPtr->GetId() <<std::endl;
	}

	return resultado.str();
}

void Carril::Dibujar(SDL_Surface *screen)
{
	double factorTramoSobrante=1.1;
	//double anchoCarril= this->getFondo()->getImagen()->h;	
	//double largoCarril= this->getFondo()->getImagen()->w;
				
	Punto* puntoActual  = this->listaDePuntos.at(0);
	 	for (int i=1; i < (int) this->listaDePuntos.size(); i++){
			Punto* puntoSiguiente  = this->listaDePuntos.at(i);

			Textura *texturaTMP=this->getFondo()->Clone();
			
			double deltaX = (puntoSiguiente->getPosX() - puntoActual->getPosX());
			double deltaY = (puntoSiguiente->getPosY() - puntoActual->getPosY());
			
			double largo= sqrt(pow(deltaX,2) + pow(deltaY,2));
		
	//		texturaTMP->cargar(largo, texturaTMP->getImagen()->h );

			texturaTMP->redimensionar(1, largo/texturaTMP->getImagen()->w);


			double angulo=0;
			SDL_Rect pos;
			angulo=(180*(atan2(deltaY,deltaX)))/M_PI;
			double angRad=atan2(deltaY,deltaX);

			texturaTMP->rotarDesdeOrigen(angRad);

			SDL_Rect rect;
			rect.x = puntoActual->posXRelAPantalla(screen->h,screen->w) - (texturaTMP->getImagen()->w/2); 
			rect.y = puntoActual->posYRelAPantalla(screen->h,screen->w) - (texturaTMP->getImagen()->h/2);

			SDL_SetColorKey(texturaTMP->getImagen(), SDL_SRCCOLORKEY|SDL_RLEACCEL, SDL_MapRGB(texturaTMP->getImagen()->format,0,0,0));

			SDL_BlitSurface(texturaTMP->getImagen(), 0, screen, &rect);
			puntoActual=puntoSiguiente;
		}
}

void Carril::CargarTextura(int resAnch){ 
	switch(resAnch){

	case 640:
		this->fondo->cargar();
		//this->fondo->redimensionar(0.7,1);
		break;
	case 800:
		this->fondo->cargar();
		//this->fondo->redimensionar(0.8,1);
		break;
	case 1024:
		this->fondo->cargar();
		//this->fondo->redimensionar(1.1,1);
		break;
	case 512:
		this->fondo->cargar(98,28);
		this->fondo->redimensionar(0.7,1);
		break;
	case 320:
		this->fondo->cargar(98,28);
		this->fondo->redimensionar(0.6,1);
		break;
	default:
		this->fondo->cargar(98,28);
		this->fondo->redimensionar(0.9,1);
		break;
	}
}

void  Carril::Colision(Pelota* pelotaCarril,Pelota *pelotaSapo,bool Posicion)
{	
	pelotaSapo->setTramo(pelotaCarril->getTramo());
	pelotaSapo->setEstado(pelotaCarril->getEstado());

    //Variables para calcular la nueva posicion
	double m, b; // y = m.x + b
	double newPosX, newPosY, xAux, corrimientoX, desplazamiento, angulo, despAux;
	Punto* pIzq, *pDer;
	vector<Punto*> vPuntos = this->listaDePuntos;
	vector<Punto*>::iterator itPuntos;
    //
	vector<Pelota*> vect = this->listaDePelotas;
	vector<Pelota*>::iterator itAux;
	Pelota* pelotaAux;
	int i = 0;

	for( itAux = vect.begin() ; itAux < vect.end(); itAux++){
       
		if ((*itAux)->GetNombre() == pelotaCarril->GetNombre()){
			pelotaSapo->setEstaEnCarril(true);
			if ( !Posicion && ((*itAux) != vect.back()) ){
				itAux++;
				i++;
			};
			break;
		}
		i++;
	};
	pelotaAux = vect[i];
	pelotaSapo->setPosX((*itAux)->getPosX());
	pelotaSapo->setPosY((*itAux)->getPosY());
	pelotaSapo->SetPuntoDer( (*itAux)->GetPuntoDer() );
	pelotaSapo->SetPuntoIzq( (*itAux)->GetPuntoIzq() );
	if ((*itAux) == vect.back())
		vect.push_back(pelotaSapo);
	else
		vect.insert(itAux , pelotaSapo);

    for( itAux = vect.begin() + i + 1; itAux < vect.end(); itAux++){
      
		pIzq = (*itAux)->GetPuntoIzq();
		pDer = (*itAux)->GetPuntoDer();
		this->Recta(pIzq, pDer, &m, &b);
		corrimientoX = CalcularDesplazamientoX( (*itAux)->getRadio(), m );
		if ( pDer->getPosX() < (*itAux)->getPosX() )
			desplazamiento = corrimientoX * (-1);//Cambio el sentido de movimiento
		else
			desplazamiento = corrimientoX;//Sentido positivo
		// Si al correr la pelota queda fuera del tramo y el tramo va en sentido +
		if ( (((*itAux)->getPosX() + desplazamiento) > pDer->getPosX() ) && (desplazamiento > 0) )
		{
			angulo  = atan( m ); //Calculo el angulo del tramo
			xAux    = pDer->getPosX() - (*itAux)->getPosX(); //Cantidad hasta terminar el tramo
			despAux = xAux / cos(angulo);//Distancia recorrida hasta fin de tramo
			//Cambio de Tramo de Carril
			pIzq = pDer;
			vPuntos = this->getListaDePuntos();
			for (itPuntos = vPuntos.begin(); itPuntos < vPuntos.end(); itPuntos++)
			{
				if( pIzq->GetId() == (*itPuntos)->GetId())
				{//Buscar el proximo punto
					itPuntos++;
					if ( (*itPuntos != NULL))
					{
					pDer = (*itPuntos);
					//Cambio la pelota de tramo del Carril
					(*itAux)->SetPuntoIzq(pIzq);
					(*itAux)->SetPuntoDer(pDer);
					(*itAux)->setPosX(pIzq->getPosX());
					(*itAux)->setPosY(pIzq->getPosY());
					break;
					}
				}
			}
			pIzq = (*itAux)->GetPuntoIzq();
			pDer = (*itAux)->GetPuntoDer();
			
			this->Recta(pIzq, pDer, &m, &b);
			corrimientoX = this->CalcularDesplazamientoX( ((*itAux)->getRadio() - despAux), m);
			if (pDer->getPosX() < pIzq->getPosX())
				desplazamiento = corrimientoX * (-1);
			else
				desplazamiento = corrimientoX;
			newPosX = (*itAux)->getPosX() + desplazamiento;
			newPosY = m * newPosX + b;
			(*itAux)->setPosX(newPosX);
			(*itAux)->setPosY(newPosY);
			this->setListaDePelotas(vect);
			continue;

		}
		// Si al correr la pelota queda fuera del tramo y el tramo va en sentido -
		if ( (((*itAux)->getPosX() + desplazamiento) < pDer->getPosX()) && (desplazamiento < 0))
		{
			angulo  = atan( m ); //Calculo el angulo del tramo
			xAux    = abs(pDer->getPosX() - (*itAux)->getPosX()); //Cantidad hasta terminar el tramo
			despAux = xAux / cos(angulo);//Distancia recorrida hasta fin de tramo
			//Cambio de Tramo de Carril
			pIzq = pDer;
			vPuntos = this->getListaDePuntos();
			for (itPuntos = vPuntos.begin(); itPuntos < vPuntos.end(); itPuntos++)
			{
				if( pIzq->GetId() == (*itPuntos)->GetId())
				{//Buscar el proximo punto
					itPuntos++;
					pDer = (*itPuntos);
					//Cambio la pelota de tramo del Carril
					(*itAux)->SetPuntoIzq(pIzq);
					(*itAux)->SetPuntoDer(pDer);
					(*itAux)->setPosX(pIzq->getPosX());
					(*itAux)->setPosY(pIzq->getPosY());
					break;
				}
			}
			pIzq = (*itAux)->GetPuntoIzq();
			pDer = (*itAux)->GetPuntoDer();
			
			this->Recta(pIzq, pDer, &m, &b);
			corrimientoX = this->CalcularDesplazamientoX( ((*itAux)->getRadio() - despAux), m);
			if (pDer->getPosX() < pIzq->getPosX())
				desplazamiento = corrimientoX * (-1);
			else
				desplazamiento = corrimientoX;
			newPosX = (*itAux)->getPosX() + desplazamiento;
			newPosY = m * newPosX + b;
			(*itAux)->setPosX(newPosX);
			(*itAux)->setPosY(newPosY);
			this->setListaDePelotas(vect);
			continue;

		}
			
		newPosX = (*itAux)->getPosX() + desplazamiento;
		newPosY = m * newPosX + b;
		(*itAux)->setPosX(newPosX);
		(*itAux)->setPosY(newPosY);
	}
	//Asigno el vector terminado
	this->setListaDePelotas(vect);
}


Pelota* Carril::eliminoPelotas(Pelota* pelo)
{
	int pts=0;

	vector<Pelota*> vect = this->listaDePelotas;
	vector<Pelota*>::iterator itAux;
    int i,inicio,fin,cant;
	bool resultado = false;
	bool cambio = true;
    Pelota* aux;
	Pelota* pelotaJuntada = NULL;
	i = 0;
	cant=1;
	int tramoNuevo ;
	itAux = vect.begin();
	bool eliminar = false;
	
	tramoNuevo = (*itAux)->getTramo() ;
	for( itAux = vect.begin() ; itAux < vect.end(); itAux++){
	
		if ( i == 0 ){
			aux = (*itAux);
		};
		if (( aux->getTramo() == (*itAux)->getTramo()) && (i>0)){
		//	if (( ((*itAux) -1)->getFondo()->GetIdTextura() == (*itAux)->getFondo()->GetIdTextura()) ){
			if (( aux->getFondo()->GetIdTextura() == (*itAux)->getFondo()->GetIdTextura()) ){
		  
			   cant++;
			   if ( ( aux == pelo) || ((*itAux) == pelo) ){

					eliminar = true;
			   };
			   if (cant == 2){
			    	inicio = i-1;			    
			   };
			   cambio = false;
		   
		    }else{
		/*	   cant = 1;*/
			   fin = i;
			   cambio = true;
			}
		    if (( cant > 2 ) && ( cambio || ((*itAux) == vect.back()) ) && eliminar){

			    //if ((*itAux) == vect.back()){
			    //   fin = i+1; //i+1;	
			    //};
				fin = inicio + cant;
				float numeroloko=cant-3;
				pts = (100*cant) + pow(5,numeroloko); 
				this->setPuntosCarril(pts);

				vect.erase(vect.begin()+inicio, vect.begin()+fin);
                resultado = true;
                break;
		    };
			if (cambio) {
				cant = 1;
			};
		 };
	     i++;	
		 aux = (*itAux);
	}; // end for

	tramoNuevo = tramoNuevo + 1;
	int f = inicio;
	if ( (vect.size() != inicio)  && (resultado==true)){
		for( itAux = vect.begin()+inicio ; itAux < vect.end(); itAux++){
            
			if ((*itAux) != vect.back()){
				if ((*itAux)->getTramo() != vect.at(f)->getTramo()){
                   (*itAux)->setEstado(false);
			       (*itAux)->setTramo(tramoNuevo);
					break;
				}
                (*itAux)->setEstado(false);
   		       (*itAux)->setTramo(tramoNuevo);
			}else{
			(*itAux)->setEstado(false);
			(*itAux)->setTramo(tramoNuevo);
			}
		f++;
		}
	}

	this->setListaDePelotas(vect);

	if (inicio>=1){
	   if ( vect.at(inicio -1) != vect.back() ){ 
	      if (resultado == true && ( vect.at(inicio-1)->getFondo()->GetIdTextura() == vect.at(inicio)->getFondo()->GetIdTextura()) )
	      {	
		     pelotaJuntada = this->GetListaDePelotas().at(inicio - 1); // inicio -1
		     return pelotaJuntada;
	      }else{
		     return NULL;
	      }
	   }
	}
		return NULL;
	
 

} //fin eliminar


void Carril::MoverInverso(Pelota* pelotaDesde)
{
	//SR
	bool reacTram = false;
	//Distancia q se moveran las pelotas por ciclo
	bool comenzar = false;
	double desplazamiento, despAux; //Pixels
	double corrimientoX; //Dani: Cambiar dsp
	vector<Pelota*>::iterator itPelotas;
	int i = 0;//Cantidad de iteraciones
			
	//Variables para calcular la nueva posicion
	double m, b; // y = m.x + b
	double newPosX, newPosY;
	double x1,x2,y1,y2,dist,xAux,angulo;
	Punto* pIzq, *pDer;
	vector<Punto*> vPuntos = this->listaDePuntos;
	vector<Punto*>::iterator itPuntos;

	//
	vector<Pelota*> vect = this->listaDePelotas;
	vector<Pelota*>::iterator itAux;
	//
	Pelota* pelotaHasta;
	Pelota* pelotaAnt;
	bool entro = false;
	int da = 0;

	//for(this->listaDePelotas.begin(); itPelotas != this->listaDePelotas.end(); itPelotas++)
	for(itAux = vect.begin(); itAux < vect.end(); itAux++){

		//(*itAux)->setTramo(vect.at(i-1)->getTramo());
		if (i > 0){
		if ( (*itAux)->GetNombre() == pelotaDesde->GetNombre() )
		{
			pelotaHasta = vect.at(i-1);
			pelotaAnt = vect.at(i);
			comenzar = true;//Comenzar desde la pelota correspondiente
		}
		}
		if ( comenzar )
		{
            //INICIO SR
			if (!reacTram){
				if (da > 0){
					if ( vect.at(i) == vect.back())
					{
						/*vect.at(i)->setTramo(pelotaAnt->getTramo());*/
						(*itAux)->setTramo(pelotaAnt->getTramo());
					}else
						if ( vect.at(i)->getTramo() == vect.at(i+1)->getTramo())
						{
							(*itAux)->setTramo(pelotaAnt->getTramo());
						
						}else{
							(*itAux)->setTramo(pelotaAnt->getTramo());
							reacTram = true;
						}

					}
				//
				da++;
			}
			
			//FIN SR
			pIzq = pelotaHasta->GetPuntoIzq();
			pDer = pelotaHasta->GetPuntoDer();
			(*itAux)->setPosX(pelotaHasta->getPosX());
			(*itAux)->setPosY(pelotaHasta->getPosY());
			(*itAux)->SetPuntoIzq(pelotaHasta->GetPuntoIzq());
			(*itAux)->SetPuntoDer(pelotaHasta->GetPuntoDer());
			this->Recta(pIzq, pDer, &m, &b); //Recta que describe el tramo
			corrimientoX = this->CalcularDesplazamientoX(pelotaHasta->getRadio(), m);
			//Si el tramo se mueve en sentido negativo
			if ( pDer->getPosX() < (*itAux)->getPosX() )
				desplazamiento = corrimientoX * (-1);//Cambio el sentido de movimiento
			else
				desplazamiento = corrimientoX;//Sentido positivo
			
			if ( (((*itAux)->getPosX() + desplazamiento) > pDer->getPosX() ) && (desplazamiento > 0) )
		{
			angulo  = atan( m ); //Calculo el angulo del tramo
			xAux    = pDer->getPosX() - (*itAux)->getPosX(); //Cantidad hasta terminar el tramo
			despAux = xAux / cos(angulo);//Distancia recorrida hasta fin de tramo
			//Cambio de Tramo de Carril
			pIzq = pDer;
			vPuntos = this->getListaDePuntos();
			for (itPuntos = vPuntos.begin(); itPuntos < vPuntos.end(); itPuntos++)
			{
				if( pIzq->GetId() == (*itPuntos)->GetId())
				{//Buscar el proximo punto
					itPuntos++;
					pDer = (*itPuntos);
					//Cambio la pelota de tramo del Carril
					(*itAux)->SetPuntoIzq(pIzq);
					(*itAux)->SetPuntoDer(pDer);
					(*itAux)->setPosX(pIzq->getPosX());
					(*itAux)->setPosY(pIzq->getPosY());
					break;
				}
			}
			pIzq = (*itAux)->GetPuntoIzq();
			pDer = (*itAux)->GetPuntoDer();
			
			this->Recta(pIzq, pDer, &m, &b);
			corrimientoX = this->CalcularDesplazamientoX( ((*itAux)->getRadio() - despAux), m);
			if (pDer->getPosX() < pIzq->getPosX())
				desplazamiento = corrimientoX * (-1);
			else
				desplazamiento = corrimientoX;
			newPosX = (*itAux)->getPosX() + desplazamiento;
			newPosY = m * newPosX + b;
			(*itAux)->setPosX(newPosX);
			(*itAux)->setPosY(newPosY);
			this->setListaDePelotas(vect);
			pelotaHasta = (*itAux);
			continue;

		}
		// Si al correr la pelota queda fuera del tramo y el tramo va en sentido -
		if ( (((*itAux)->getPosX() + desplazamiento) < pDer->getPosX()) && (desplazamiento < 0))
		{
			angulo  = atan( m ); //Calculo el angulo del tramo
			xAux    = abs(pDer->getPosX() - (*itAux)->getPosX()); //Cantidad hasta terminar el tramo
			despAux = xAux / cos(angulo);//Distancia recorrida hasta fin de tramo
			//Cambio de Tramo de Carril
			pIzq = pDer;
			vPuntos = this->getListaDePuntos();
			for (itPuntos = vPuntos.begin(); itPuntos < vPuntos.end(); itPuntos++)
			{
				if( pIzq->GetId() == (*itPuntos)->GetId())
				{//Buscar el proximo punto
					itPuntos++;
					pDer = (*itPuntos);
					//Cambio la pelota de tramo del Carril
					(*itAux)->SetPuntoIzq(pIzq);
					(*itAux)->SetPuntoDer(pDer);
					(*itAux)->setPosX(pIzq->getPosX());
					(*itAux)->setPosY(pIzq->getPosY());
					break;
				}
			}
			pIzq = (*itAux)->GetPuntoIzq();
			pDer = (*itAux)->GetPuntoDer();
			
			this->Recta(pIzq, pDer, &m, &b);
			corrimientoX = this->CalcularDesplazamientoX( ((*itAux)->getRadio() - despAux), m);
			if (pDer->getPosX() < pIzq->getPosX())
				desplazamiento = corrimientoX * (-1);
			else
				desplazamiento = corrimientoX;
			newPosX = (*itAux)->getPosX() + desplazamiento;
			newPosY = m * newPosX + b;
			(*itAux)->setPosX(newPosX);
			(*itAux)->setPosY(newPosY);
			this->setListaDePelotas(vect);
			pelotaHasta = (*itAux);
			continue;

		}
			
		newPosX = (*itAux)->getPosX() + desplazamiento;
		newPosY = m * newPosX + b;
		(*itAux)->setPosX(newPosX);
		(*itAux)->setPosY(newPosY);
		
		}
		i++;
		pelotaHasta = (*itAux);
	}

//ini sr	
	i=0;
	int c=1;
	Pelota* aux;
	for( itAux = vect.begin() ; itAux < vect.end(); itAux++){
		if ( i == 0 ){
			aux = (*itAux);
		};

		if ( (*itAux) == vect.back() ){
                vect.at(i)->setTramo(c);
				break;
		};
		if ( (aux->getTramo() == (*itAux)->getTramo()) && i>0) {
			vect.at(i-1)->setTramo(c); 

		};
		if ( !(aux->getTramo() == (*itAux)->getTramo()) && i>0){
			 vect.at(i-1)->setTramo(c);
			 c++;
	    };
		i++;
	    aux = (*itAux);
    };

//fin  sr

	this->setListaDePelotas(vect);
}

void Carril::BonusRetroceso(int cantidadBolas)
{
	vector<Pelota*> vect = this->listaDePelotas;
	vector<Pelota*>::iterator itAux;
	vector<Pelota*> vectAuxiliar;//Vector para guardar las posiciones de las 10
								 //primeras pelotas
	Pelota*         pelotaAux;//Pelota para cambiar posicion
	int i = 0; //Iteracion del vector
	
	Pelota* aux;
	for( itAux = vect.begin() ; itAux < vect.end(); itAux++){
	
		if ( i == 0 ){
			aux = (*itAux);
		};
		if (( aux->getTramo() != (*itAux)->getTramo()) && (i>0)){
			
			MoverInverso(aux);

		}
	    i++;	
		aux = (*itAux);
	}

	i=0;

	//Si la cantidad de pelotas es menos a cantidadBolas
	if ( this->GetListaDePelotas().size() <= cantidadBolas )
		if( this->getCantidadPelotas() <= this->getCantidadPelotasEmitidas() && (!(this->GetListaDePelotas().empty())) )
	    {
			pelotaAux = this->getPelotaAleatoria(listaDePelotasDisponibles);
			pelotaAux->setEstaEnCarril(true);
			pelotaAux->SetPuntoIzq( this->listaDePuntos[0]);
			pelotaAux->SetPuntoDer( this->listaDePuntos[1]);
			pelotaAux->setPosX( this->listaDePuntos[0]->getPosX());
			pelotaAux->setPosY( this->listaDePuntos[0]->getPosY());
			pelotaAux->setTramo( 1 );
			vect.insert(vect.begin(), pelotaAux);
			this->setListaDePelotas(vect);

			MoverInverso(vect.at(1));
			vect.erase(vect.begin());
		}
		else{
		vect.clear();//vacio el vector
		}
	else
	{
		
		vect.erase(vect.begin()+1,vect.begin()+cantidadBolas);
		this->setListaDePelotas(vect);
		vect = this->listaDePelotas;
		MoverInverso(vect.at(1));

	}
	this->setListaDePelotas(vect);
}
		
void Carril::setVelocidad(double bolasPorSegundo){
		SetPixels(bolasPorSegundo * FACTORVELOCIDAD);
}

double Carril::getVelocidad(){
	return (GetPixels() / FACTORVELOCIDAD);
}

Pelota*	Carril::GetPrimeraPelota(){

	if ((this->listaDePelotas.size() == 0) || (this->listaDePelotas.empty())) return NULL;
	else return listaDePelotas.back();
}

void Carril::BonusFreno(){
	if (((this->getVelocidad()) * (1 - AUMENTOVELOCIDAD))>=MINIMOVELOCIDAD)
	{
		this->setVelocidad((this->getVelocidad())* (1 - AUMENTOVELOCIDAD));
	}
}

void Carril::setPuntosCarril(int punt){ 

	this->puntosCarril = this->puntosCarril + punt;
	this->puntosBonus = this->puntosBonus + punt;

}

void  Carril::estadoFinal()
{
 	vector<Pelota*> vect = this->listaDePelotas;
	vector<Pelota*>::iterator itAux;

    int tramoAux; 

	tramoAux = vect.at(0)->getTramo();
	for( itAux = vect.begin() ; itAux < vect.end(); itAux++){
	
		if ( (*itAux)->getTramo() == tramoAux )
		{
		(*itAux)->setEstado(true);
		}
	}
	this->setListaDePelotas(vect);
}